home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / et / et-2_2.lha / et2.2 / src / XSERVER / XClipBoard.C < prev    next >
C/C++ Source or Header  |  1990-12-18  |  5KB  |  190 lines

  1. #include "X11.h"
  2.  
  3. #include "X11/Xatom.h"
  4.  
  5. #include "XClipBoard.h"
  6. #include "XWinSystem.h"
  7. #include "IO/membuf.h"
  8. #include "String.h"
  9. #include "Error.h"
  10. #include "View.h"
  11. #include "FileType.h"
  12.  
  13. char *cEtProperty= "_ET",
  14.      *cEtType    = "_ET_OIO";   // selection is in object input/output format
  15.  
  16. //---- XClipBoard ------------------------------------------------------------
  17.  
  18. XClipBoard::XClipBoard()
  19. {
  20.     awin= XCreateWindow(display, XRootWindow(display, screen),
  21.         0, 0, 1, 1, 0, XDefaultDepth(display, screen), InputOutput,
  22.                         (Visual*) CopyFromParent, 0, 0);
  23.     XSelectInput(display, awin, PropertyChangeMask);
  24.     etprop= XInternAtom(display, cEtProperty, XFalse);
  25.     etformat= XInternAtom(display, cEtType, XFalse);
  26. }
  27.  
  28. XClipBoard::~XClipBoard()
  29. {
  30.     XDestroyWindow(display, awin);
  31. }
  32.  
  33. bool XClipBoard::ProcessEvent(XEvent &xe)
  34. {
  35.     if (xe.xany.window != awin)
  36.     return TRUE;
  37.  
  38.     switch (xe.type) {
  39.     case SelectionClear:
  40.     if (xe.xselectionclear.selection == XA_PRIMARY) {
  41.         XDeleteProperty(display, awin, etprop);
  42.         char *t= (char*) GetType();
  43.         cerr << "NotOwner(" << t << ")\n";
  44.         NotOwner(t);
  45.     }
  46.     break;
  47.  
  48.     case SelectionRequest:
  49.     SendClipBoard((XSelectionRequestEvent*) &xe);
  50.     break;
  51.     
  52.     default:
  53.     break;
  54.     }
  55.     return FALSE;
  56. }
  57.  
  58. char *XClipBoard::DevGetType()
  59. {
  60.     XWindow selwin= XGetSelectionOwner(display, XA_PRIMARY);
  61.     if (selwin && selwin != awin) {
  62.     Atom actual_type_return;
  63.     int actual_format_return;
  64.     u_char *prop_return;
  65.     u_long nitems_return, bytes_after_return;
  66.     char *t;
  67.     XGetWindowProperty(display, selwin, etprop, 0L, 0L, XFalse,
  68.         etformat, &actual_type_return, &actual_format_return,
  69.             &nitems_return, &bytes_after_return, &prop_return);
  70.     if (actual_type_return == None && actual_format_return == 0)
  71.         t= "None";
  72.     else
  73.         t= (char*) cDocTypeET;
  74.     return t;
  75.     }
  76.     return ClipBoard::DevGetType();
  77. }
  78.  
  79. long XClipBoard::GetCurrentServerTime()
  80. {
  81.     XEvent ev;
  82.     XChangeProperty(display, awin, XA_WM_NAME, XA_STRING, 8, PropModeAppend, (byte*) "", 0);
  83.     XWindowEvent(display, awin, PropertyChangeMask, &ev);
  84.     return ((XPropertyEvent*)&ev)->time;
  85. }
  86.  
  87. void XClipBoard::ScratchChanged(char*)
  88. {
  89.     XSetSelectionOwner(display, XA_PRIMARY, awin, GetCurrentServerTime());
  90.     if (XGetSelectionOwner(display, XA_PRIMARY) != awin)
  91.     cerr << "can't get selection\n";
  92.     XChangeProperty(display, awin, etprop, etformat, 8, PropModeReplace,
  93.                                 (byte*) "", 0);
  94. }
  95.  
  96. static XBool IsSelectionNotify(XDisplay*, XEvent *xe, char*)
  97. {
  98.     return (xe->type == SelectionNotify);
  99. }
  100.  
  101. membuf *XClipBoard::MakeBuf(char *type)
  102. {
  103.     membuf *mb= 0;
  104.     XEvent ev;
  105.     XSelectionEvent *se;
  106.     Atom actual_type_return, wishtype;
  107.     int actual_format_return;
  108.     u_char *prop_return;
  109.     u_long nitems_return, bytes_after_return;
  110.     
  111.     if (type == cDocTypeET)
  112.     wishtype= etformat;
  113.     else
  114.     wishtype= XA_STRING;
  115.     
  116.     XConvertSelection(display, XA_PRIMARY, wishtype, None, awin, CurrentTime);
  117.     XIfEvent(display, &ev, IsSelectionNotify, 0);
  118.     se= (XSelectionEvent*) &ev;
  119.     
  120.     if (se->property == None) {
  121.     cerr << "can't convert selection\n";
  122.     return mb;
  123.     }
  124.     u_long len;
  125.     mb= new membuf(0);
  126.     
  127.     XGetWindowProperty(display, awin, se->property, 0L, 0L, XFalse,
  128.         AnyPropertyType, &actual_type_return, &actual_format_return,
  129.         &nitems_return, &bytes_after_return, &prop_return);
  130.         
  131.     len= bytes_after_return;
  132.     
  133.     XGetWindowProperty(display, awin, se->property, 0L, (len-1)/4+1, XTrue,
  134.         AnyPropertyType, &actual_type_return, &actual_format_return,
  135.         &nitems_return, &bytes_after_return, &prop_return);
  136.     
  137.     mb->setbuf((char*)strsave((char*)prop_return, (int)(len+1)), (int)(len+1));
  138.     XFree((char*) prop_return);
  139.     mb->seek(len, TRUE);
  140.  
  141.     return mb;
  142. }
  143.  
  144. static XBool IsPropertyDeleted(XDisplay*, XEvent *xe, char *vp)
  145. {
  146.     if (xe->type == PropertyNotify) {
  147.     XPropertyEvent *pe= (XPropertyEvent*) xe;
  148.     if (pe->window == *((XWindow*)vp) && pe->atom == XA_PRIMARY
  149.                         && pe->state == PropertyDelete)
  150.         return TRUE;
  151.     }
  152.     return FALSE;
  153. }
  154.  
  155. void XClipBoard::SendClipBoard(XSelectionRequestEvent *sre)
  156. {
  157.     XSelectionEvent sev;
  158.     XEvent ev;
  159.     
  160.     sev.type= SelectionNotify;
  161.     sev.display= sre->display;
  162.     sev.selection= sre->selection;
  163.     sev.target= sre->target;
  164.     sev.time= sre->time;
  165.     sev.property= sre->property;
  166.     sev.requestor= sre->requestor;
  167.     
  168.     if (sev.target == etformat) {
  169.     } else if (sev.target == XA_STRING) {
  170.     } else {
  171.     char *nm= XGetAtomName(display, sev.target);
  172.     Error("XClipBoard::SendClipBoard", "can't convert to %s", nm);
  173.     XFree(nm);
  174.     }
  175.        
  176.     if (sev.property == None) {
  177.     sev.property= XA_PRIMARY;
  178.     sev.target= XA_STRING;
  179.     }
  180.     
  181.     XChangeProperty(display, sev.requestor, sev.property, sev.target, 8,
  182.       PropModeReplace, (byte*) GetBuf()->Base(), (int) GetBuf()->tell(TRUE));
  183.       
  184.     XSelectInput(display, sev.requestor, PropertyChangeMask);
  185.     XSendEvent(display, sev.requestor, XFalse, 0, (XEvent*) &sev);
  186.     XFlush(display);
  187.     XCheckIfEvent(display, &ev, IsPropertyDeleted, (char*) &sev.requestor);
  188. }
  189.  
  190.